package com.um.jdy.mp.station.manager;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.date.DateUtil;
import cn.hutool.json.JSONUtil;
import com.um.jdy.common.device.code.DeviceCode;
import com.um.jdy.common.device.entity.po.Pile;
import com.um.jdy.common.device.entity.po.Station;
import com.um.jdy.common.device.service.PileService;
import com.um.jdy.common.device.service.StationService;
import com.um.jdy.common.platform.code.PartnersCode;
import com.um.jdy.common.platform.entity.po.Merchant;
import com.um.jdy.common.platform.service.CompanyService;
import com.um.jdy.common.platform.service.MerchantService;
import com.um.jdy.common.system.entity.po.Param;
import com.um.jdy.common.system.service.ParamService;
import com.um.jdy.mp.base.entity.vo.StationItemVO;
import com.um.jdy.mp.station.entity.dto.AddressDTO;
import com.um.jdy.mp.station.entity.dto.EditStationDTO;
import com.um.jdy.mp.station.entity.vo.EditStationVO;
import com.um.jdy.mp.station.entity.vo.ParamItemVO;
import com.um.jdy.mp.station.entity.vo.StationDevice;
import com.um.jdy.mp.user.service.SessionUserService;
import com.um.springboot.starter.code.CommonCode;
import com.um.springboot.starter.entity.Page;
import com.um.springboot.starter.exception.ServiceException;
import com.um.springboot.starter.orm.entity.Response;
import com.um.springboot.starter.orm.manager.BaseManager;
import com.um.springboot.starter.orm.params.ListParams;
import com.um.springboot.starter.orm.params.PageParams;
import com.um.springboot.starter.service.MapService;
import com.um.springboot.starter.utils.StringUtil;
import com.um.springboot.starter.utils.UMBeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;

/**
 * 管理类：站场
 *
 * @author cs
 * 日期 2023/5/24
 * 版权所有 广州优匠科技有限公司
 */
@Component
public class StationManager extends BaseManager<StationService> {

    @Autowired
    SessionUserService sessionUserService;

    @Autowired
    CompanyService companyService;

    @Autowired
    SessionUserService companyUserService;

    @Autowired
    PileService pileService;

    @Autowired
    MerchantService merchantService;

    @Autowired
    ParamService paramService;

    @Autowired
    MapService mapService;

    /**
     * 列表
     * @param params
     * @return
     */
    public Response<List<StationItemVO>> list(ListParams params) {
        params.getCondition().put("s.com_id", getComId());
        params.getCondition().put("s.platform_merchant_id", sessionUserService.getTokenUserId());
        List<StationItemVO> list = service.getCMSViewModelListBySqlName("get_station_list", StationItemVO.class, params.getProperties(), params.getValues(), params.getRangeEntitys(), params.getOrderNames(), params.getSortOns());
        list.forEach(row->{
            row.setStationDevices(service.getViewModelList("get_station_device_count", StationDevice.class,new String[]{row.getDeviceStationId(),getComId()}));
        });
        return Response.success(list);
    }

    /**
     * 列表
     * @param params
     * @return
     */
    public Response<List<StationItemVO>> getSharingStationList(ListParams params) {
        params.getCondition().put("s.com_id", getComId());
        params.getCondition().put("ss.platform_merchant_id", sessionUserService.getTokenUserId());
        List<StationItemVO> list = service.getCMSViewModelListBySqlName("get_sharing_station_list", StationItemVO.class, params.getProperties(), params.getValues(), params.getRangeEntitys(), params.getOrderNames(), params.getSortOns());
        return Response.success(list);
    }

    /**
     * 分页列表
     * @param params
     * @return
     */
    public Response<Page<StationItemVO>> page(PageParams params) {
        Page<StationItemVO> page = new Page();
        page.setPageNo(params.getPageNo());
        page.setPageSize(params.getPageSize());

        params.getCondition().put("s.com_id", getComId());
        params.getCondition().put("s.platform_merchant_id", sessionUserService.getTokenUserId());

        page = service.getCMSViewModelPageBySqlName(page, "get_station_page", "get_station_count",
                StationItemVO.class, params.getProperties(), params.getValues(), params.getRangeEntitys(), params.getOrderNames(), params.getSortOns());
        page.getResult().forEach(row->{
            row.setStationDevices(service.getViewModelList("get_station_device_count", StationDevice.class,new String[]{row.getDeviceStationId(),getComId()}));
        });
        return Response.success(page);
    }

    /**
     * 详情
     * @param id
     * @return
     */
    public Response<EditStationVO> get(String id) {

        checkPermission(id);

        Station station = this.service.getEntity(id);
        EditStationVO vo = UMBeanUtils.copyBean(station, EditStationVO.class);

        try {
            vo.setLabelList(JSONUtil.toList(station.getLabelItems(), String.class));
        }catch (Exception e){
            vo.setLabelList(new ArrayList<>());
        }
        try {
            vo.setServiceList(JSONUtil.toList(station.getServiceItems(), String.class));
        }catch (Exception e){
            vo.setServiceList(new ArrayList<>());
        }
        return Response.success(vo);
    }

    /**
     * 新增
     * @param dto
     * @return
     */
    @Transactional
    public Response<Station> add(EditStationDTO dto) {
        //验证分账比例不超上级
        Merchant merchant = merchantService.getEntity(companyUserService.getTokenUserId());
        if(!StringUtil.getTrim(merchant.getParentId()).equals("")){
            Merchant agent = merchantService.getEntity(merchant.getParentId());
            if(agent != null && agent.getCommissionRate() < merchant.getCommissionRate()){
                throw new ServiceException(PartnersCode.RateNotLargeThanParent);
            }
        }

        Station station = BeanUtil.toBean(dto, Station.class);
        if(StringUtil.isEmpty(station.getThumb()) && !StringUtil.isEmpty(station.getThumbs())){
            List thumbs = JSONUtil.parseArray(station.getThumbs());
            if(thumbs.size() > 0){
                station.setThumb(StringUtil.getTrim(thumbs.get(0)));
            }
        }

        station.setPlatformMerchantId(companyUserService.getTokenUserId());
        station.setCreateUserId(companyUserService.getTokenUserId());
        station.setLabelItems(JSONUtil.toJsonStr(dto.getLabelList()));
        station.setServiceItems(JSONUtil.toJsonStr(dto.getServiceList()));;
        station.setCreateTime(DateUtil.date());
        station.setCommissionRate(merchant.getCommissionRate());
        //保存充电站
        service.save(station);
        return Response.success(station);
    }

    /**
     * 更新
     * @param id
     * @param dto
     * @return
     */
    @Transactional
    public Response<Station> update(String id, EditStationDTO dto) {

        checkPermission(id);

        Station station =  service.getEntity("device_station_id", id);
        if (null == station) {
            throw new ServiceException(DeviceCode.NoStation);
        }

        //验证分账比例不超上级
//        Merchant merchant = merchantService.getEntity(companyUserService.getTokenUserId());
//        if(!StringUtil.getTrim(merchant.getParentId()).equals("")){
//            Merchant agent = merchantService.getEntity(merchant.getParentId());
//            if(agent != null && agent.getCommissionRate() < dto.getCommissionRate()){
//                throw new ServiceException(PartnersCode.RateNotLargeThanParent);
//            }
//        }

        BeanUtil.copyProperties(dto, station);
        if(StringUtil.isEmpty(station.getThumb()) && !StringUtil.isEmpty(station.getThumbs())){
            List thumbs = JSONUtil.parseArray(station.getThumbs());
            if(thumbs.size() > 0){
                station.setThumb(StringUtil.getTrim(thumbs.get(0)));
            }
        }
        station.setDeviceStationId(id);
        station.setLabelItems(JSONUtil.toJsonStr(dto.getLabelList()));
        station.setServiceItems(JSONUtil.toJsonStr(dto.getServiceList()));
        //保存充电站
        service.save(station);
        return Response.success(station);
    }

//    @Transactional
//    public Response deleteIds(List<String> ids) {
//        boolean result = service.deleteIds(ids);
//        ids.stream().forEach(id -> {
//            recyclePiles(id);
//        });
//        return result ? Response.success() : Response.failed();
//    }

    @Transactional
    public Response delete(String deviceStationId) {

        checkPermission(deviceStationId);

        boolean result =  service.delete(deviceStationId);
        recyclePiles(deviceStationId);
        return result ? Response.success() : Response.failed();
    }

    /**
     * 回收桩列表
     *
     * @param stationId
     */
    private void recyclePiles(String stationId) {
        List<Pile> piles = pileService.getList("device_station_id", stationId);
        piles.stream().forEach(pile -> {
            pile.setDeviceStationId("");
            pileService.update(pile);
        });
    }

    /**
     * 关键词输入提示
     * @param param
     * @return
     */
    public Response searchAddress(AddressDTO param){
        return Response.success(mapService.searchAddress(param.getKeyword(),null));
    }


    /**
     * 场地类型列表
     * @return
     */
    public Response<List<ParamItemVO>> getTypeList(){
        List<Param> params = paramService.getList("path","station.location","sort_no","asc");
        return Response.success(toParamItemList(params));
    }

    /**
     * 场地类型列表
     * @return
     */
    public Response<List<ParamItemVO>> getLabelList(){
        List<Param> params = paramService.getList("path","station.label_items","sort_no","asc");
        return Response.success(toParamItemList(params));
    }

    /**
     * 场地类型列表
     * @return
     */
    public Response<List<ParamItemVO>> getServiceList(){
        List<Param> params = paramService.getList("path","station.service_items","sort_no","asc");
        return Response.success(toParamItemList(params));
    }

    private List<ParamItemVO> toParamItemList(List<Param> params){
        List<ParamItemVO> list = new ArrayList<>();

        for(Param param : params){
            ParamItemVO itemVO = new ParamItemVO();
            itemVO.setLabel(param.getPValue());
            itemVO.setValue(param.getPKey());
            list.add(itemVO);
        }

        return list;
    }

    /**
     * 校验数据权限
     * @param id
     */
    private void checkPermission(String id){
        Station station = service.getEntity(id);
        if(station == null)
            throw new ServiceException(DeviceCode.NoStation);

        if(!StringUtil.equals(sessionUserService.getTokenUserId(),station.getPlatformMerchantId()))
            throw new ServiceException(CommonCode.NoDataPermission);
    }
}
